Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix active window not working on the framebuffer #94

Open
wants to merge 2 commits into
base: main
Choose a base branch
from

Conversation

weihsinyeh
Copy link
Collaborator

Remove the inefficiently function twin_active_pixmap(). This function finds the currently and previously active window pixel map by traversing the list of pixel maps. This function will be called every time the screen needs to be updated. Set the active variable of the window only when the window's event TwinEventButtonDown is triggered to avoid redundant operations. Additionally, implement the function twin_window_active_paint() to only repaint the title bar instead of calling the function twin_window_draw() to indirectly call the function twin_window_frame to repaint the title bar of the window.

Close #92

Remove the inefficiently function twin_active_pixmap(). This function
finds the currently and previously active window pixel map by traversing
the list of pixel maps. This function will be called every time the
screen needs to be updated. Set the active variable of the window only
when the window's event TwinEventButtonDown is triggered to avoid
redundant operations. Additionally, implement the function
twin_window_active_paint() to only repaint the title bar instead of
calling the function twin_window_draw() to indirectly call the function
twin_window_frame to repaint the title bar of the window.

Close sysprog21#92

Signed-off-by: Wei-Hsin Yeh <[email protected]>
src/window.c Outdated
@@ -156,6 +156,19 @@ void twin_window_set_name(twin_window_t *window, const char *name)
strcpy(window->name, name);
twin_window_draw(window);
}
static void twin_window_active_paint(twin_window_t *window)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Missing one empty line here.

@shengwen-tw
Copy link
Collaborator

Looks legitimate to me, but since I am not familiar with recent developments, I would like to see if others have different opinions.

@huaxinliao
Copy link
Collaborator

huaxinliao commented Jan 26, 2025

I confirmed that fbdev can run on a VM with Ubuntu 24.04 and a Pi 3B. Below is the output from the Pi 3B.

test.mp4

@weihsinyeh
Copy link
Collaborator Author

The title bars of the active and inactive window don't display on the video.

src/window.c Outdated
twin_fixed_t bw_2 = bw / 2;
if (window->active) {
twin_paint_path(window->pixmap, TWIN_ACTIVE_BG, path);
twin_paint_stroke(window->pixmap, TWIN_ACTIVE_BORDER, path, bw_2 * 2);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The reason that the title bars don't show is because you need to determine the trajectory you want to paint first and then use twin_paint_path or twin_paint_stroke to fill the graph or draw the border.

I think the twin_window_active_paint would be like

static void twin_window_active_paint(twin_window_t *window)
{
    // Ignore the above
    twin_path_t *path = twin_path_create();
    twin_path_move(path, c_left, c_top);
    twin_path_draw(path, c_right, c_top);
    twin_path_curve(path, c_right, w_top + t_arc_1, c_right - t_arc_1, w_top,
                    c_right - t_h, w_top);
    twin_path_draw(path, c_left + t_h, w_top);
    twin_path_curve(path, c_left + t_arc_1, w_top, c_left, w_top + t_arc_1,
                    c_left, c_top);
    twin_path_close(path);
    if (window->active) {
        twin_paint_path(window->pixmap, TWIN_ACTIVE_BG, path);
        twin_paint_stroke(window->pixmap, TWIN_ACTIVE_BORDER, path, bw_2 * 2);
    } else {
        twin_paint_path(window->pixmap, TWIN_INACTIVE_BG, path);
        twin_paint_stroke(window->pixmap, TWIN_INACTIVE_BORDER, path, bw_2 * 2);
    }
}

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you! It seems that using the "twin_window_frame()" function directly is still the better option. Originally, I thought this just changed the BG and border colors. But since there is no path record, it is not sure where to apply the colors.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How about adding a twin_path_t *label_path member to twin_window_t? In twin_window_frame, you could initialize the path, and in twin_window_active_paint, determine the color to paint when the top window changes. Then you can still apply the colors in the same logic.

static void twin_window_active_paint(twin_window_t *window)
{
    twin_fixed_t bw = twin_int_to_fixed(TWIN_TITLE_BW);
    twin_path_t *path = twin_path_create();
    twin_fixed_t bw_2 = bw / 2;
    if (window->active) {
        twin_paint_path(window->pixmap, TWIN_ACTIVE_BG, window->label_path);
        twin_paint_stroke(window->pixmap, TWIN_ACTIVE_BORDER, window->label_path, bw_2 * 2);
    } else {
        twin_paint_path(window->pixmap, TWIN_INACTIVE_BG, window->label_path);
        twin_paint_stroke(window->pixmap, TWIN_INACTIVE_BORDER, window->label_path, bw_2 * 2);
    }
}

static void twin_window_frame(twin_window_t *window)
{
    /* Ignore the above */
    window->label_path = twin_path_create();
    twin_path_move(window->label_path, c_left, c_top);
    twin_path_draw(window->label_path, c_right, c_top);
    twin_path_curve(window->label_path, c_right, w_top + t_arc_1, c_right - t_arc_1, w_top,
                    c_right - t_h, w_top);
    twin_path_draw(window->label_path, c_left + t_h, w_top);
    twin_path_curve(window->label_path, c_left + t_arc_1, w_top, c_left, w_top + t_arc_1,
                    c_left, c_top);
    twin_path_close(window->label_path);
    twin_window_active_paint(window);
}

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

OK, Thank you! we can try which one can work on framebuffer.

When the box is trigger by TwinEventButtonDown, its window's title bar
needs to change color and be put onto the toppest layer. However, after
removing the implementation of changing the color of window's title bar
from the function twin_screen_update(), it will only be putted onto the
toppest layer. Therefore, add the twin_window_frame() to update the
color when box is triggered by TwinEventButtonDown.
@huaxinliao
Copy link
Collaborator

Here's the output from 512a891 on the Pi 3B.

drm.mp4

@@ -1173,6 +1173,8 @@ void twin_window_damage(twin_window_t *window,
twin_coord_t right,
twin_coord_t bottom);

void twin_window_frame(twin_window_t *window);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Add comments.

@jserv jserv requested a review from ndsl7109256 January 29, 2025 12:31
@@ -157,7 +157,7 @@ void twin_window_set_name(twin_window_t *window, const char *name)
twin_window_draw(window);
}

static void twin_window_frame(twin_window_t *window)
void twin_window_frame(twin_window_t *window)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why did you change this function from static to non-static?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Unexpected null screen in Linux framebuffer backend
5 participants